﻿package fwk.form.elements{
	
	import flash.display.MovieClip;
	import flash.display.DisplayObjectContainer;
	import flash.display.DisplayObject;
	import flash.display.Stage;
	import flash.events.Event;
	import flash.events.MouseEvent;
	import flash.events.FocusEvent;
	import flash.events.KeyboardEvent;
	import flash.ui.Keyboard;
	
	import fwk.scrollBars.*;
	
	import flash.utils.getDefinitionByName;
	


	public class QuestionComboBox extends AbstractQuestion 
	{
		private var _comboBox:MovieClip;
		private var _itemSelected:ReponseComboBox;
		
		private var _opened:Boolean = false;
		
		private var _textPromp:String = "";
		private var _posy:Number = 0;
		private var _currentIndexSelected:int = -1;
		
		private var _scrollBar:ScrollBar;
		private var _heightListCombo:int = 150;
		private var _stage:Stage;
		
		public function QuestionComboBox(mc:MovieClip = null, pstage:Stage = null) 
		{

			_stage = pstage;
			
			super(mc);
			
			trace("--> instance de QuestionComboBox");
			_comboBox = this.mc.input as MovieClip;
			
			_tabReponses = new Array();
			opened = false;
			
			_comboBox.texte.mouseEnabled = false;
			_comboBox.picto.mouseEnabled = false;
			_comboBox.texte.mouseChildren = false;
			_comboBox.picto.mouseChildren = false;
			
			_comboBox.fond.buttonMode = true;
			_comboBox.fond.addEventListener(MouseEvent.CLICK, onClickPicto);
			
			_comboBox.addEventListener(FocusEvent.FOCUS_IN, onFocusIn);
			_comboBox.addEventListener(FocusEvent.FOCUS_OUT, onFocusOut);
			
			
		}
		private function onFocusIn(e:FocusEvent):void 
		{
			_comboBox.stage.addEventListener(KeyboardEvent.KEY_DOWN, _onKeyDown);
			
			if (shapeFocus) {
				spriteFocus.graphics.clear();
				spriteFocus.graphics.beginFill(colorShapeFocus, 0.2);
				spriteFocus.graphics.drawRect( - 3,  - 3, _comboBox.fond.width + 6, _comboBox.fond.height + 6);
				_comboBox.addChildAt(spriteFocus, 0);
			}
		}
		private function onFocusOut(e:FocusEvent):void 
		{
			_comboBox.stage.removeEventListener(KeyboardEvent.KEY_DOWN, _onKeyDown);
			if (shapeFocus) _comboBox.removeChild(spriteFocus);
		}
		private function _onKeyDown(e:KeyboardEvent):void 
		{
			
			if ( e.keyCode == Keyboard.RIGHT || e.keyCode == Keyboard.DOWN)
			{
				if ( _currentIndexSelected + 1 < _tabReponses.length) {
					select( _tabReponses[_currentIndexSelected+1]);
				}
				
			}else if ( e.keyCode == Keyboard.LEFT || e.keyCode == Keyboard.UP)
			{
				if ( _currentIndexSelected - 1 >= 0) {
					select( _tabReponses[_currentIndexSelected-1]);
				}
			}
			
			
		}
		
		
		
		public function getItemAt(index:int):ReponseComboBox
		{
			if( index < _tabReponses.length)
				return _tabReponses[index] as ReponseComboBox;
			else 
				return null;
			
		}
		public function getItem(id:String):ReponseComboBox
		{

			for (var i:int = 0; i < _tabReponses.length; i++) 
			{
				var rep:ReponseComboBox = _tabReponses[i];
				if (  rep.id == id) {
					return rep;
				}
			}
			
			return null;
			
		}
		private function onClickStage(e:MouseEvent):void 
		{
			
			
			if ( _comboBox.stage != null) {
				
				if ( _comboBox.mouseX > _comboBox.width || _comboBox.mouseX < 0 || _comboBox.mouseY < 0 || _comboBox.mouseY > _comboBox.height) {
					if (_opened)
					{
						opened = false;
					}
				}
			}
			

		}
		
		private function onClickPicto(e:MouseEvent):void 
		{
			
			hideError();
			if (_opened)
			{
				opened = false;
			}else {
				opened = true;
			}
			
		}
		


		public function init(xmlConfig:XML)
		{
			super._init(xmlConfig);
			
			
			
			_heightListCombo = _comboBox.contenu.fond.height;
			
			// efface les eventuelles item déja créés
			var nbItem:int = _tabReponses.length;
			for (var i:int = 0; i < nbItem; i++) 
			{
				_comboBox.contenu.container.removeChild(_tabReponses[i].mc);
			}
			
			// init list item
			_tabReponses = new Array();
			
			removeAllChild(_comboBox.contenu.container);
			
			for (var j:int = 0; j < xmlConfig.children().length(); j++) {

				
				// ajout réponse
				var node:XML = xmlConfig.children()[j];
				
				var cl:Class = getDefinitionByName(node.@idLibrary) as Class;
				var mcItem:MovieClip = new cl() as MovieClip;
				var rep:ReponseComboBox = new ReponseComboBox(mcItem);
						
				rep.value = node.@value;
				//rep.type = type;
				rep.id = node.@id;
				
				//trace("rep.type " + rep.type);
				
				addReponse(rep);
				
				if (node.@selected != null && node.@selected == "true") {
					select(rep);
				}
				
				
			}
			
						
		}
		

		override public function set tabIndex(value:int):void 
		{
			if (value == -1) {
				_comboBox.tabEnabled = false;
			}else {
				_comboBox.tabEnabled = true;
			}
			
			_comboBox.tabIndex = value;
			
		}
		
		
		//----------------------------------------------------------
		//---- Efface tous les enfants d' un clip
		//----------------------------------------------------------
		public static function removeAllChild(clip:Object) {			
			if(clip != null && clip is DisplayObjectContainer){
				var i:uint = 0;
				var nb:uint = clip.numChildren;
				var obj:DisplayObject;
				
				var tabToDelete:Array = new Array();

				for (i = 0; i < nb; i++)
				{
					obj = clip.getChildAt(i);
					tabToDelete.push(obj);
				}
				// delete clip
				nb = tabToDelete.length;
				for (i = 0; i < nb; i++) {
					obj = tabToDelete[i];
					clip.removeChild(obj);
				}
			}
		}
		
		public function deleteList():void
		{
			
			reset();
			
			// init list item
			_tabReponses = new Array();

			_posy = 0;
						
			removeAllChild(_comboBox.contenu.container);
			
			initScroll();
			
		}
		
		override public function reset():void
		{
			hideError();
			
			_itemSelected = null;
			opened = false;
			
			_comboBox.texte.tTexte.text = textPromp;
		}
		
		public function resizeCombo():void
		{
			_comboBox.fond.width = _comboBox.texte.x*2 + _comboBox.texte.width + comboBox.picto.width;
			_comboBox.picto.x = _comboBox.fond.width - _comboBox.picto.width;
			
			
			var nbRep:int = reponsesTab.length;
			var maxWidthContenu:Number = 0;
			
			for (var i:int = 0; i < nbRep; i++)
			{
				var widthRep:Number = reponsesTab[i].mc.texte.x * 2 + reponsesTab[i].mc.texte.width;
				if (  widthRep > maxWidthContenu)
				{
					maxWidthContenu = widthRep;
				}
			}
			
			if ( _scrollBar != null && _scrollBar.mcScroll.visible) maxWidthContenu += _scrollBar.mcScroll.width;
			
			if (  maxWidthContenu < _comboBox.fond.width) {
				maxWidthContenu = _comboBox.fond.width;
			}
			_comboBox.contenu.fond.width = maxWidthContenu;
			
			if ( _scrollBar != null && _scrollBar.mcScroll.visible) maxWidthContenu -= _scrollBar.mcScroll.width;
			for (i = 0; i < nbRep; i++)
			{
				reponsesTab[i].mc.fond.clip.width = maxWidthContenu;

			}
			
			initScroll();

			

			
		}
		public function initScroll():void
		{
			
			if (  _comboBox.contenu.scroll != null)
			{
				if ( _scrollBar == null) {
					_scrollBar = new ScrollBar(_comboBox.contenu.scroll);
					_scrollBar.contenu = _comboBox.contenu.container;
					trace("_heightListCombo " + _heightListCombo);
					_scrollBar.sizeToScroll = _heightListCombo;
					_scrollBar.marge = 0;
					_scrollBar.stage = _stage;
					_scrollBar.create();
				}
				
				_scrollBar.maskScroll.width = _comboBox.contenu.container.width;
				_scrollBar.init();
			}
		}
		
		public function setTextItemAt(texte:String, index:int)
		{
			_comboBox.replaceItemAt({label: texte, data: _comboBox.getItemAt(index).data}, index);
		}
		
		
		//--------------------------------------------------------
		override public function addReponse(itemRep:AbstractReponse)
		{

			itemRep.addEventListener(MouseEvent.CLICK, onClickItem);
			
			_comboBox.contenu.container.addChild(itemRep.mc);
			itemRep.mc.y = _posy;
			
			_posy += itemRep.mc.height;
			
			if ( _posy > _heightListCombo && _scrollBar != null) _comboBox.contenu.fond.height = _heightListCombo;
			else _comboBox.contenu.fond.height = _posy;
			
			super.addReponse(itemRep);
			
			resizeCombo();
		}
		

		
		private function onClickItem(e:MouseEvent):void 
		{
			var item:ReponseComboBox = e.currentTarget as ReponseComboBox;
			
			select(item);
			
			opened = false;
			
			trace("reponse selected "  + _itemSelected.id);
			dispatchEvent(new Event(Event.CHANGE));
		}
		
		//--------------------------------------------------------
		public function select(rep:ReponseComboBox):void
		{
			
			for (var i:int = 0; i < _tabReponses.length; i++) 
			{
				var rep2:ReponseComboBox = _tabReponses[i];
				if (  rep.id == rep2.id)
				{
					hideError();
					if (_itemSelected != null) _itemSelected.selected = false;
					_itemSelected = rep2;
					_itemSelected.selected = true;
					_currentIndexSelected = i;
					
					//texte
					_comboBox.texte.tTexte.text = _itemSelected.mc.texte.tTexte.text;
				}
			}
		}
		
		override public function get reponse():AbstractReponse
		{ 
			return _itemSelected;
			
		}
		public function get itemSelected():AbstractReponse
		{ 
			return _itemSelected;
			
		}
		
		public function get opened():Boolean { return _opened; }
		
		public function set opened(value:Boolean):void 
		{
			_opened = value;
			_comboBox.contenu.visible = _opened;
			
			trace("_opened " + _opened);
			
			if (_opened)
			{
				_comboBox.stage.addEventListener(MouseEvent.CLICK, onClickStage);
				if(_scrollBar != null) _scrollBar.init();
			}else {
				
				if(_scrollBar != null)  _scrollBar.removeListeners();
				
				try {
					_comboBox.stage.removeEventListener(MouseEvent.CLICK, onClickStage);
				}catch (e) {
					
				}

			}
		}
		
		
		
		public function get listItem():Array { return _tabReponses; }
		
		public function get comboBox():MovieClip { return _comboBox; }
		
		public function get textPromp():String { return _textPromp; }
		
		public function set textPromp(value:String):void 
		{
			_textPromp = value;
		}
		

		override public function set rollOver(value:Boolean):void 
		{
			if ( _rollOver != value) {
				_rollOver = value;
				
				if ( _rollOver) {
					_mc.input.fond.addEventListener(MouseEvent.MOUSE_OVER, onMouseOver);
					_mc.input.fond.addEventListener(MouseEvent.MOUSE_OUT, onMouseOut);
				}else {
					_mc.input.fond.removeEventListener(MouseEvent.MOUSE_OVER, onMouseOver);
					_mc.input.fond.removeEventListener(MouseEvent.MOUSE_OUT, onMouseOut);
				}
			}
		}
		
		public function get heightListCombo():int { return _heightListCombo; }
		
		public function set heightListCombo(value:int):void 
		{
			_heightListCombo = value;
		}
		override public function onMouseOut(e:MouseEvent):void 
		{
			if ( hasLabel("out", _mc.input) && _mc.input.currentLabel != "out")
			{
				_mc.input.gotoAndPlay("out");
			}
		}
		
		override public function onMouseOver(e:MouseEvent):void 
		{
			if ( hasLabel("over", _mc.input) &&  _mc.input.currentLabel != "over")
			{
				_mc.input.gotoAndPlay("over");
			}
		}
		
	}
}